package qmlt.dataset.filter;

import java.util.List;

import qmlt.dataset.DataSetBase;
import qmlt.dataset.DataSet;
import qmlt.dataset.Instance;
import qmlt.dataset.utils.DataSetUtils;
import qmlt.dataset.utils.ListUtils;

public class GaussianNormalizationFilter implements Filter
{

	private float[]	means;

	private float[]	stds;

	@Override
	public DataSet filter(DataSet ds)
	{
		// dim info
		int n = ds.getInstances().size();
		int m = ds.getFeatureDefs().size();

		means = new float[m];
		stds = new float[m];

		for (int i = 0; i < m; ++i)
		{
			List<Float> values = ListUtils.convert(DataSetUtils.getFeatureColumn(ds.getInstances(), i));
			means[i] = (float) ListUtils.mean(values);
			stds[i] = (float) ListUtils.std(values, means[i]);
		}

		// write data
		DataSet newDs = new DataSetBase(ds.getDef().clone(ds.getId() + "-gnorm"), ds);
		for (int i = 0; i < n; ++i)
		{
			Instance inst = ds.getInstances().get(i);
			Instance newInst = new Instance(inst.id, newDs);

			for (int j = 0; j < m; ++j)
			{
				newInst.getFeatures().add(((Float) inst.getFeatures().get(j) - means[j]) / stds[j]);
			}
			newInst.setTarget(inst.getTarget());
			newDs.getInstances().add(newInst);
		}

		return newDs;
	}

}
